#pragma once
#include <set>
#include <string>
#include <map>
#include "listener_handler.h"
#include "client_connection.h"
#include "game_base_msg.h"
#include "db_client_handler.h"
class BaseGame;
class Service;
class Listener;
class JMsgProto;
class DBClient;
class BasePlayer;
class BaseRoom;
class BaseGameImpl : public ClientConnectionHandler, public ListenerHandler, public DBClientHandler
{
public:
	BaseGameImpl(void);
	~BaseGameImpl(void);
	void start();
	void stop();

	virtual void onStart();
	virtual void onStop();
	void setBaseGame(BaseGame* baseGame);
private:
	virtual void onClientHeartBeatTimeout(ClientConnectionHandler* handler);
	virtual void onClientDisconnect(ClientConnection* conn);
public:
	virtual void onAccept(Connection* conncetion);
public:
	
public:
	virtual void onClientConnected(ClientConnection* conn);
	virtual void onClientData(ClientConnection* conn, int mainCmd, int subCmd, void* data, int len);
	virtual bool onClientDisconnected(ClientConnection* conn);

public:
	virtual void onDBConnected(DBClient* client);
	virtual void onDBDisconnected(DBClient* client);

	virtual void onDBPlayerInfoResponse(DBMsgPlayerInfoResponse* response);
	virtual void onDBMsgAddRegisterPlayerResponse(DBMsgAddRegisterPlayerResponse* resp);
	virtual void onDBMsgActivatePlayerResponse(DBMsgActivatePlayerResponse* resp);

private:
	void procRoomSystemMsg(ClientConnection* conn, void* data, int len);
	void procRoomUserMsg(ClientConnection* conn, void* data, int len);
	void procDeskSystemMsg(ClientConnection* conn, void* data, int len);
	void procDeskUserMsg(ClientConnection* conn, void* data, int len);
	void procPlayerLoginMsg(ClientConnection* conn, BaseMsgC2SLogin* msg);
	void procPlayerJoinRoomMsg(ClientConnection* conn, BaseMsgC2SJoinRoom* msg);
	void procPlayerJoinDeskMsg(ClientConnection* conn, BaseMsgC2SJoinDesk* msg);
	void procPlayerCreateFriendDeskMsg(ClientConnection* conn, BaseMsgC2SCreateFriendDesk* msg);
	void procPlayerJoinFriendDeskMsg(ClientConnection* conn, BaseMsgC2SJoinFriendDesk* msg);
	void procPlayerLeaveDeskMsg(ClientConnection* conn, BaseMsgC2SLeaveDesk* msg);
	void procPlayerRegister(ClientConnection* conn, BaseMsgC2SRegister* msg);
	void procPlayerActivate(ClientConnection* conn, BaseMsgC2SActivate* msg);
	void procPlayerUpdateRoomStatus(ClientConnection* conn, BaseMsgC2SUpdateRoomStatus* msg);
	void procPlayerLeaveRoom(ClientConnection* conn, BaseMsgC2SLeaveRoom* msg);
	void procPlayerUpdatePlayerInfo(ClientConnection* conn, BaseMsgC2SUpdatePlayerData* msg);
private:
	BasePlayer* attachConnectionAndCreateUser(ClientConnection* conn, std::string userName);
	void detachConnectionFromPlayer(BasePlayer* player, bool addConnToUnAuth = false);
private:
	Listener* m_listener;
	Service* m_service;
	std::set<ClientConnection*> m_setUnAuthConnections;
	std::map<std::string, BasePlayer*> m_userNameToPlayer;
	JMsgProto* m_proto;
	JMsgProto* m_dbProto;
	DBClient* m_dbClient;
	BaseGame* m_baseGame;
	BaseRoom* m_room;
	
};
